home *** CD-ROM | disk | FTP | other *** search
/ MacUser ROM 45 / MACUSER-ROM-VOL-45-1997-08.ISO.7z / MACUSER-ROM-VOL-45-1997-08.ISO / 本誌連動 / 第9回:ウイークエンドデベロッパーへの道 / QuickCinema 1.0 / Source code / MovieTheater.c < prev    next >
Text File  |  1997-04-28  |  14KB  |  428 lines

  1. /*------------------------------------------------------------------------------
  2. *    プログラム名:    QuickCinema 1.0.0
  3. *    ファイル名:        MovieTheater.c
  4. *-----------------------------------------------------------------------------*/
  5.  
  6. #include "QuickCinema.h"
  7. #include "ProtoType.h"
  8.  
  9. //----------------------------------------------------------------------------------//
  10. //            定数定義                                                                //
  11. //----------------------------------------------------------------------------------//
  12.  
  13. //----------------------------------------------------------------------------------//
  14. //            グローバル変数                                                            //
  15. //----------------------------------------------------------------------------------//
  16.  
  17. extern Boolean                gQuitApplication;
  18. extern Boolean                gIsBackground;
  19. extern SInt32                gSleepTime;
  20. extern AEAddressDesc        gSelfAddress;
  21.  
  22. //----------------------------------------------------------------------------------//
  23. //            プロトタイプ                                                            //
  24. //----------------------------------------------------------------------------------//
  25.  
  26. static OSErr LoadMovieFile(MovieInfoHandle movieInfoHdl, Movie *theMovie);
  27. static Boolean ShowMovieWindow(Movie theMovie, MovieInfoHandle movieInfoHdl);
  28. static Boolean IsOpenedMovieFIle(const FSSpec *fileSpec);
  29.  
  30. //----------------------------------------------------------------------------------//
  31. // ムービーに対するイベント処理                                                        //
  32. //----------------------------------------------------------------------------------//
  33. Boolean HandleMovieTask(const EventRecord *event)
  34. {
  35.     WindowRef                window;
  36.     MovieInfoHandle         movieInfoHdl;
  37.     MovieController            controller;
  38.     Boolean                    catchedEvent = false;
  39.     
  40.     window = FrontWindow();
  41.     while (window != nil)
  42.     {
  43.         // ムービーウィンドウであるか確認する
  44.         if (IsMovieWindow(window))
  45.         {
  46.             movieInfoHdl = (MovieInfoHandle)GetWRefCon(window);
  47.             if (movieInfoHdl)
  48.             {
  49.                 controller = (*movieInfoHdl)->controller;
  50.                 // ムービーに対するイベント処理をコントローラに委ねる
  51.                 if (MCIsPlayerEvent(controller, event))
  52.                     catchedEvent = true;
  53.             }
  54.         }
  55.         window = (WindowPtr)(((WindowPeek)window)->nextWindow);
  56.     }
  57.     // コントローラがイベントを処理した場合:true
  58.     // コントローラがイベントを処理しなかった場合:false
  59.     return catchedEvent;    
  60. }
  61.  
  62. //----------------------------------------------------------------------------------//
  63. // ムービー専用編集メニュー処理                                                        //
  64. //----------------------------------------------------------------------------------//
  65. void HandleMovieEditMenu(WindowRef window, short menuItem)
  66. {
  67.     MovieInfoHandle         movieInfoHdl;
  68.     MovieController            controller;
  69.     Movie                     aMovie = nil;
  70.     ComponentResult            compErr;
  71.     
  72.     movieInfoHdl = (MovieInfoHandle)GetWRefCon(window);
  73.     controller = (*movieInfoHdl)->controller;
  74.  
  75.     switch (menuItem)
  76.     {
  77.         // Undoメニュー項目を処理する
  78.         case iUndo:
  79.             compErr = MCUndo(controller);
  80.             break;
  81.         // Cutメニュー項目を処理する 選択したムービーが返される
  82.         case iCut:
  83.             aMovie = MCCut(controller);
  84.             break;
  85.         // Copyメニュー項目を処理する 選択したムービーが返される
  86.         case iCopy:
  87.             aMovie = MCCopy(controller);
  88.             break;
  89.         // Pasteメニュー項目を処理する
  90.         case iPaste:
  91.             compErr = MCPaste(controller, nil);
  92.             break;
  93.         // Clearメニュー項目を処理する
  94.         case iClear:
  95.             compErr = MCClear(controller);
  96.             break;
  97.     }
  98.     if (aMovie)
  99.     {
  100.         // 取得したムービーをスクラップに保存する
  101.         PutMovieOnScrap(aMovie, 0);
  102.         DisposeMovie(aMovie);
  103.     }
  104. }
  105.  
  106. //----------------------------------------------------------------------------------//
  107. // ムービーファイル選択処理                                                            //
  108. //----------------------------------------------------------------------------------//
  109. Boolean HandleOpenMovie(void)
  110. {
  111.     StandardFileReply        reply;
  112.     OSType                    fileType = MovieFileType;
  113.     Movie                    movieFilm = nil;
  114.     MovieInfoHandle            movieInfoHdl = nil;
  115.     GrafPtr                    savedPort;
  116.     
  117.     GetPort(&savedPort);
  118.     SetCursor(&qd.arrow);
  119.     
  120.     // プレビュー付ファイル選択ダイアログを表示する
  121.     StandardGetFilePreview(nil, 1, &fileType, &reply);
  122.     SetPort(savedPort);
  123.     // キャンセルされた場合は処理を中断する
  124.     if (reply.sfGood == false)
  125.         return false;
  126.     // 選択したムービーが既に開かれているかチェックする
  127.     if (IsOpenedMovieFIle(&reply.sfFile))
  128.         return true;
  129.         
  130.     movieInfoHdl = (MovieInfoHandle)NewHandleClear(sizeof(MovieInfoRec));
  131.     if ((MemError() != noErr) || (movieInfoHdl == nil))
  132.         return false;
  133.     // ムービー情報を初期化する    
  134.     (*movieInfoHdl)->controller = nil;
  135.     (*movieInfoHdl)->windowType = MovieFileType;
  136.     BlockMove(&reply.sfFile, &(*movieInfoHdl)->movieFileSpec, sizeof(FSSpec));
  137.     // ファイルからムービーを読み込む
  138.     if (LoadMovieFile(movieInfoHdl, &movieFilm) != noErr)
  139.     {
  140.         DisposeHandle((Handle) movieInfoHdl);
  141.         
  142.         AlertUser(eCantCreateTheater);
  143.         return false;
  144.     }
  145.     // ムービーウィンドウとコントローラを生成する            
  146.     if (ShowMovieWindow(movieFilm, movieInfoHdl) == false)
  147.     {    
  148.         if ((*movieInfoHdl)->controller)
  149.             DisposeMovieController((*movieInfoHdl)->controller);
  150.         if (movieFilm)
  151.             DisposeMovie(movieFilm);
  152.             
  153.         DisposeHandle((Handle) movieInfoHdl);
  154.         
  155.         AlertUser(eCantCreateTheater);
  156.         return false;
  157.     }
  158.     
  159.     return true;
  160. }
  161.  
  162. //----------------------------------------------------------------------------------//
  163. // ムービーファイルの読込処理                                                        //
  164. //----------------------------------------------------------------------------------//
  165. Boolean HandleReadMovieFile(FSSpec *fileSpec)
  166. {
  167.     FInfo                    fndrInfo;
  168.     Movie                    movieFilm = nil;
  169.     MovieInfoHandle            movieInfoHdl = nil;
  170.     
  171.     if (FSpGetFInfo(fileSpec, &fndrInfo) != noErr)
  172.         return false;
  173.     // ムービーファイルであるかチェックする
  174.     if (fndrInfo.fdType != MovieFileType)
  175.         return false;
  176.     // 該当ムービーが既に開かれているかチェックする
  177.     if (IsOpenedMovieFIle(fileSpec))
  178.         return true;
  179.         
  180.     movieInfoHdl = (MovieInfoHandle)NewHandleClear(sizeof(MovieInfoRec));
  181.     if ((MemError() != noErr) || (movieInfoHdl == nil))
  182.         return false;
  183.     // ムービー情報を初期化する    
  184.     (*movieInfoHdl)->controller = nil;
  185.     (*movieInfoHdl)->windowType = MovieFileType;
  186.     BlockMove(fileSpec, &(*movieInfoHdl)->movieFileSpec, sizeof(FSSpec));
  187.     // ファイルからムービーを読み込む
  188.     if (LoadMovieFile(movieInfoHdl, &movieFilm) != noErr)
  189.     {
  190.         DisposeHandle((Handle) movieInfoHdl);
  191.         
  192.         AlertUser(eCantCreateTheater);
  193.         return false;
  194.     }
  195.     // ムービーウィンドウとコントローラを生成する            
  196.     if (ShowMovieWindow(movieFilm, movieInfoHdl) == false)
  197.     {    
  198.         if ((*movieInfoHdl)->controller)
  199.             DisposeMovieController((*movieInfoHdl)->controller);
  200.         if (movieFilm)
  201.             DisposeMovie(movieFilm);
  202.             
  203.         DisposeHandle((Handle) movieInfoHdl);
  204.         
  205.         AlertUser(eCantCreateTheater);
  206.         return false;
  207.     }    
  208.         
  209.     return true;
  210. }
  211.  
  212. //----------------------------------------------------------------------------------//
  213. // ムービーデータの取得処理                                                            //
  214. //----------------------------------------------------------------------------------//
  215. static OSErr LoadMovieFile(MovieInfoHandle movieInfoHdl, Movie *theMovie)
  216. {
  217.     SInt16                    movieRef, resID = 0;
  218.     OSErr                    err;
  219.     
  220.     *theMovie = nil;
  221.     // ムービーファイルを開く
  222.     err = OpenMovieFile(&(*movieInfoHdl)->movieFileSpec, &movieRef, fsRdPerm);
  223.     if (err != noErr)
  224.         return err;
  225.     // ファイルからムービーを読み込む    
  226.     err = NewMovieFromFile(theMovie, movieRef, &resID, nil, newMovieActive, nil);
  227.     // ムービーファイルを閉じる
  228.     (void) CloseMovieFile(movieRef);
  229.         
  230.     return err;
  231. }
  232.  
  233. //----------------------------------------------------------------------------------//
  234. // ムービー再生用ウィンドウ生成                                                        //
  235. //----------------------------------------------------------------------------------//
  236. static Boolean ShowMovieWindow(Movie theMovie, MovieInfoHandle movieInfoHdl)
  237. {
  238.     WindowRef                window;
  239.     Rect                    bounds;
  240.     MovieController            controller = nil;
  241.     ComponentResult            compErr;
  242.     
  243.     window = GetNewCWindow(rMovieWindow, nil, (WindowRef)-1L);
  244.     
  245.     if (window != nil)
  246.     {    
  247.         // ムービー情報をウィンドウのRefconに格納する
  248.         SetWRefCon(window, (SInt32)movieInfoHdl);    
  249.         // ムービーを表示するグラフィック環境を準備する    
  250.         SetMovieGWorld(theMovie, (CGrafPtr)window, nil);
  251.         // ムービーの境界矩形を取得する
  252.         GetMovieBox(theMovie, &bounds);
  253.         // 上記矩形を座標 (0,0)にフィックスする
  254.         OffsetRect(&bounds, -bounds.left, -bounds.top);
  255.         // ムービーの境界矩形を再設定する
  256.         SetMovieBox(theMovie, &bounds);
  257.         // ムービーサイズにフィットしたコントローラを生成する
  258.         controller = NewMovieController(theMovie, &bounds, mcTopLeftMovie);
  259.         if (controller != nil)
  260.         {
  261.             // コントローラの境界矩形を取得する
  262.             compErr = MCGetControllerBoundsRect(controller, &bounds);
  263.             if (compErr == noErr)
  264.             {
  265.                 (*movieInfoHdl)->controller = controller;
  266.                 // コントローラのキー入力を可能にする
  267.                 compErr = MCDoAction(controller, mcActionSetKeysEnabled,
  268.                                     (void *)true);
  269.                 // コントローラにグローボックスを表示する                
  270.                 compErr = MCDoAction(controller, mcActionSetGrowBoxBounds, 
  271.                                     &qd.screenBits.bounds);
  272.                 // グローボックス処理のためにイベントフィルタを準備する                
  273.                 compErr = MCSetActionFilterWithRefCon(controller, 
  274.                                 NewMCActionFilterWithRefConProc(ControllerFilter),
  275.                                 (long) window);
  276.                 // コントローラの編集機能を有効にする            
  277.                 MCEnableEditing(controller, true);
  278.                 // コントローラの幅にウィンドウを合わせる
  279.                 SizeWindow(window, bounds.right, bounds.bottom, false);
  280.                 // 最適なウィンドウ画面サイズに調整する
  281.                 AlignWindow(window, false, nil, nil);
  282.                 // ウィンドウタイトルを設定する
  283.                 if ((*movieInfoHdl)->movieFileSpec.name[0] > 0)
  284.                     SetWTitle(window, (*movieInfoHdl)->movieFileSpec.name);
  285.                 // ウィンドウを表示する    
  286.                 ShowWindow(window);
  287.             }    return true;
  288.         }
  289.         CloseTheWindow(window);            
  290.     }
  291.     return false;
  292. }
  293.  
  294. //----------------------------------------------------------------------------------//
  295. // ムービー情報の破棄                                                                //
  296. //----------------------------------------------------------------------------------//
  297. void DisposeMovieWindow(WindowRef window)
  298. {
  299.     MovieInfoHandle         movieInfoHdl;
  300.     Movie                    movieFilm;
  301.     
  302.     movieInfoHdl = (MovieInfoHandle)GetWRefCon(window);
  303.     if (movieInfoHdl != nil)
  304.     {
  305.         // コントローラからムービーを取得する
  306.         movieFilm = MCGetMovie((*movieInfoHdl)->controller);
  307.         
  308.         // コントローラを破棄する
  309.         if ((*movieInfoHdl)->controller)
  310.             DisposeMovieController((*movieInfoHdl)->controller);
  311.         // ムービーを破棄する
  312.         if (movieFilm)
  313.             DisposeMovie(movieFilm);
  314.         // ムービー情報を破棄する    
  315.         DisposeHandle((Handle) movieInfoHdl);
  316.         // ムービーウィンドウを破棄する
  317.         DisposeWindow(window);
  318.     }    
  319. }
  320.  
  321. //----------------------------------------------------------------------------------//
  322. // ムービーウィンドウのアクティベートイベント処理                                    //
  323. //----------------------------------------------------------------------------------//
  324. void HandleMovieActivate(WindowRef window, Boolean becomeActive)
  325. {
  326.     MovieInfoHandle         movieInfoHdl;
  327.     MovieController            controller;
  328.     ComponentResult            compErr;
  329.     GrafPtr                    savedPort;
  330.     
  331.     GetPort(&savedPort);
  332.     SetPort(window);
  333.     
  334.     movieInfoHdl = (MovieInfoHandle)GetWRefCon(window);
  335.     if (movieInfoHdl != nil)
  336.     {
  337.         controller = (*movieInfoHdl)->controller;
  338.         // コントローラのアクティベート状態を設定する
  339.         compErr = MCActivate(controller, window, becomeActive);
  340.     }
  341.     SetPort(savedPort);
  342. }
  343.  
  344. //----------------------------------------------------------------------------------//
  345. // ムービーアクションプロック                                                        //
  346. //----------------------------------------------------------------------------------//
  347. pascal Boolean ControllerFilter(MovieController theController, 
  348.                             short action, void *params, long refCon)
  349. {
  350. #pragma unused (params)
  351.  
  352.     Rect                    bounds;
  353.     
  354.     switch (action) 
  355.     {
  356.         // グローボックスに対する処理を実行する
  357.         case  mcActionControllerSizeChanged:
  358.             // コントローラの境界矩形を取得する
  359.             MCGetControllerBoundsRect(theController, &bounds);
  360.             // 新しい境界矩形にウィンドウサイズを変更する
  361.             SizeWindow((WindowRef) refCon, 
  362.                     bounds.right - bounds.left, bounds.bottom - bounds.top, true);
  363.             break;
  364.     }
  365.     return false;
  366. }
  367.  
  368. //----------------------------------------------------------------------------------//
  369. // ムービーウィンドウの確認処理                                                        //
  370. //----------------------------------------------------------------------------------//
  371. Boolean IsMovieWindow(WindowRef window)
  372. {
  373.     MovieInfoHandle            movieInfoHdl = nil;
  374.     
  375.     if (window == nil)
  376.         return false;
  377.     movieInfoHdl = (MovieInfoHandle)GetWRefCon(window);
  378.     if (movieInfoHdl == nil)
  379.         return false;
  380.     // ウィンドウがムービー情報を記録していることを確認する    
  381.     if ((*movieInfoHdl)->windowType == MovieFileType)
  382.         return true;
  383.     else
  384.         return false;
  385. }
  386.  
  387. //----------------------------------------------------------------------------------//
  388. // 既に開いているムービーファイルであるかチェック                                    //
  389. //----------------------------------------------------------------------------------//
  390. static Boolean IsOpenedMovieFIle(const FSSpec *fileSpec)
  391. {
  392.     Boolean                    alreadyOpened = false;
  393.     WindowRef                window;
  394.     MovieInfoHandle            movieInfoHdl = nil;
  395.     
  396.     window = FrontWindow();
  397.     if (window == nil)
  398.         return alreadyOpened;
  399.     
  400.     // 現在表示中の全ウィンドウを順番に評価する
  401.     do
  402.     {
  403.         // ムービーウィンドウであることをチェックする
  404.         if (IsMovieWindow(window))
  405.         {
  406.             movieInfoHdl = (MovieInfoHandle)GetWRefCon(window);
  407.             if (movieInfoHdl != nil)
  408.             {
  409.                 // ファイル情報が一致した場合は既に開いていることを意味する
  410.                 if ((fileSpec->vRefNum == (*movieInfoHdl)->movieFileSpec.vRefNum)
  411.                     &&    (fileSpec->parID == (*movieInfoHdl)->movieFileSpec.parID)
  412.                     && (IUEqualString(fileSpec->name, 
  413.                         (*movieInfoHdl)->movieFileSpec.name) == 0))
  414.                 {
  415.                     // 該当ウィンドウを前面に移動する
  416.                     SelectWindow(window);
  417.                     alreadyOpened = true;
  418.                 }
  419.             }
  420.         }
  421.         // 次のウィンドウを取得する
  422.         window = GetNextWindow(window);
  423.         
  424.     } while ((window != nil) && (alreadyOpened == false));
  425.     
  426.     return alreadyOpened;
  427. }
  428.